From: Felix Fietkau Date: Wed, 28 May 2025 22:07:47 +0000 (+0200) Subject: interface: ask for unicast responses by default X-Git-Url: http://git.openwrt.org/%22https:/collectd.org//%22http:/www.crowdsec.net/%22/%22https:/collectd.org/%22http:/www.crowdsec.net/%22?a=commitdiff_plain;h=55d0c1bc1ac594af413e2d94a56e21b0d78346dc;p=project%2Fmdnsd.git interface: ask for unicast responses by default When able to bind the socket without REUSEPORT, unicast responses can be received on the main port. Indicate that in outgoing questions in order to reduce unnecessary multicast traffic. Signed-off-by: Felix Fietkau --- diff --git a/dns.c b/dns.c index 7c24ddc..18210f1 100644 --- a/dns.c +++ b/dns.c @@ -185,7 +185,7 @@ void dns_packet_send(struct interface *iface, struct sockaddr *to, bool query, i if (query) { if (multicast < 0) - multicast = interface_multicast(iface); + multicast = iface->need_multicast; for (i = 0; i < pkt_n_q; i++) dns_question_set_multicast(pkt_q[i], multicast); diff --git a/interface.c b/interface.c index 944666f..e2f0ce9 100644 --- a/interface.c +++ b/interface.c @@ -478,7 +478,7 @@ iface_update_cb(struct vlist_tree *tree, struct vlist_node *node_new, interface_start(if_new); } -static int interface_init_socket(enum umdns_socket_type type) +static int interface_init_socket(enum umdns_socket_type type, bool *mcast) { struct sockaddr_in6 local6 = { .sin6_family = AF_INET6 @@ -492,6 +492,7 @@ static int interface_init_socket(enum umdns_socket_type type) int no = 0; int fd; int af = (type & SOCKTYPE_BIT_IPV6) ? AF_INET6 : AF_INET; + bool reuseport = false; if (ufd[type].fd >= 0) return 0; @@ -501,9 +502,6 @@ static int interface_init_socket(enum umdns_socket_type type) return -1; setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(yes)); -#ifdef SO_REUSEPORT - setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &yes, sizeof(yes)); -#endif switch (type) { case SOCK_UC_IPV4: @@ -524,6 +522,7 @@ static int interface_init_socket(enum umdns_socket_type type) break; } +retry: if (type & SOCKTYPE_BIT_IPV6) { ufd[type].cb = read_socket6; if (bind(fd, (struct sockaddr *)&local6, sizeof(local6)) < 0) @@ -545,6 +544,14 @@ static int interface_init_socket(enum umdns_socket_type type) return 0; error: + if (!reuseport) { +#ifdef SO_REUSEPORT + setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &yes, sizeof(yes)); +#endif + reuseport = true; + *mcast = true; + goto retry; + } close(ufd[type].fd); return -1; } @@ -555,9 +562,10 @@ __interface_add(const char *name, enum umdns_socket_type type, { struct interface *iface; unsigned int ifindex; + bool mcast = false; char *id_buf; - if (interface_init_socket(type)) + if (interface_init_socket(type, &mcast)) goto error; ifindex = if_nametoindex(name); @@ -572,6 +580,7 @@ __interface_add(const char *name, enum umdns_socket_type type, iface->ifindex = ifindex; iface->type = type; iface->addrs = *list; + iface->need_multicast = mcast; vlist_add(&interfaces, &iface->node, id_buf); return; diff --git a/interface.h b/interface.h index aca2f41..0c37736 100644 --- a/interface.h +++ b/interface.h @@ -52,6 +52,7 @@ struct interface { const char *name; enum umdns_socket_type type; + bool need_multicast; int ifindex; struct interface_addr_list addrs;